// src/renderer/models/factories/SerialPortFactory.ts
import type {
  AngleRpmRequest,
  HttpRequest,
  OpenSerialRequest,
  SerialRequest,
  WriteRequest,
  SpeedRequest,
  LoadInfoRequest,
  AngleLimitRequest,
  VoltageLimitRequest,
  AngleRequest,
  AccelerationDecelerationRequest,
} from '../up_request.ts';
import type { BaseResponse } from '../up_response.ts';
import { SerialError } from '../up_error';

export class SerialPortFactory {
  private static checkProtocolId(protocol_id: number) {
    if (protocol_id < 0 || protocol_id > 255) {
      throw new Error('protocol_id must be between 0 and 255.');
    }
  }

  static createOpenSerialRequest(
    device: string,
    baudrate: number,
    parity: string,
    databits: number,
    stopbits: number,
    flowcontrol: string,
    timeout: number
  ): OpenSerialRequest {
    return {
      device,
      baudrate,
      parity,
      databits,
      stopbits,
      flowcontrol,
      timeout,
    };
  }

  static createSerialRequest(serial_id: string): SerialRequest {
    return { serial_id };
  }

  static createHttpRequest(
    serial_id: string,
    protocol_id: number
  ): HttpRequest {
    this.checkProtocolId(protocol_id);
    return { serial_id, protocol_id };
  }

  static createWriteRequest(serial_id: string, raw_data: string): WriteRequest {
    return { serial_id, raw_data };
  }

  static createAngleRequest(
    serial_id: string,
    protocol_id: number,
    angle: number
  ): AngleRequest {
    this.checkProtocolId(protocol_id);
    return { serial_id, protocol_id, angle };
  }

  static createAngleRpmRequest(
    serial_id: string,
    protocol_id: number,
    angle: number,
    rpm: number
  ): AngleRpmRequest {
    this.checkProtocolId(protocol_id);
    return { serial_id, protocol_id, angle, rpm };
  }

  static createAngleLimitRequest(
    serial_id: string,
    protocol_id: number,
    min: number,
    max: number
  ): AngleLimitRequest {
    this.checkProtocolId(protocol_id);
    return { serial_id, protocol_id, min, max };
  }

  static createVoltageLimitRequest(
    serial_id: string,
    protocol_id: number,
    min: number,
    max: number
  ): VoltageLimitRequest {
    this.checkProtocolId(protocol_id);
    return { serial_id, protocol_id, min, max };
  }

  static createSpeedRequest(
    serial_id: string,
    protocol_id: number,
    rpm: number
  ): SpeedRequest {
    this.checkProtocolId(protocol_id);
    return { serial_id, protocol_id, rpm };
  }

  static createLoadInfoRequest(
    serial_id: string,
    protocol_id: number,
    interval: number
  ): LoadInfoRequest {
    this.checkProtocolId(protocol_id);
    return { serial_id, protocol_id, interval };
  }

  static createSerialError(message: string, code: number = 3000): SerialError {
    return new SerialError(message, code);
  }

  static createSerialErrorResponse(
    message: string,
    code: number = 3000
  ): BaseResponse<SerialError> {
    return {
      status: false,
      code,
      message,
      data: this.createSerialError(message, code),
    };
  }

  static createAccelerationDecelerationRequest(
    serial_id: string,
    protocol_id: number,
    acceleration: number,
    deceleration: number
  ): AccelerationDecelerationRequest {
    this.checkProtocolId(protocol_id);
    return { serial_id, protocol_id, acceleration, deceleration };
  }
}
